/*
 * Copyright (c) 2020 - present, Inspur Genersoft Co., Ltd.
 *
 * Licensed under the Apache License, Version 2.0 (the "License");
 * you may not use this file except in compliance with the License.
 * You may obtain a copy of the License at
 *
 *       http://www.apache.org/licenses/LICENSE-2.0
 *
 * Unless required by applicable law or agreed to in writing, software
 * distributed under the License is distributed on an "AS IS" BASIS,
 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
 * See the License for the specific language governing permissions and
 * limitations under the License.
 */

package io.iec.edp.caf.msu.server;

import io.iec.edp.caf.msu.api.entity.ServiceUnitInfo;
import io.iec.edp.caf.msu.api.server.MsuServiceDiscovery;
import io.iec.edp.caf.msu.server.balance.MsuServiceLoadBalance;
import io.iec.edp.caf.msu.server.storage.MsuStorage;
import io.iec.edp.caf.msu.server.storage.database.domain.entity.GspMsuRegisterInfo;
import io.iec.edp.caf.tenancy.api.context.MultiTenantContextInfo;
import io.iec.edp.caf.tenancy.core.context.MultiTenantContextHolder;
import lombok.extern.slf4j.Slf4j;
import lombok.var;

import java.util.ArrayList;
import java.util.List;

/**
 * @author Leon Huo
 */
@Slf4j
public class MsuServiceDiscoveryImpl implements MsuServiceDiscovery {
    private MsuStorage storage;
    private MsuServiceLoadBalance loadBalance;

    public MsuServiceDiscoveryImpl(MsuStorage storage, MsuServiceLoadBalance loadBalance) {
        this.storage = storage;
        this.loadBalance = loadBalance;
    }

    /**
     * 根据app和su获取servicename
     *
     * su平铺到nacos后应该没啥用了
     * @param appName
     * @param serviceUnitName
     * @return
     */
    @Override
    public String discover(String appName, String serviceUnitName) {
        serviceUnitName = serviceUnitName.toLowerCase();

        List<String> storageInfo = new ArrayList<>();
        try{

            //msu的注册默认注册到主库
            MultiTenantContextInfo contextInfo = new MultiTenantContextInfo();
            contextInfo.setMasterDb(true);
            MultiTenantContextHolder.set(contextInfo);
            storageInfo = this.storage.getMsuServiceList(appName, serviceUnitName);

        }finally {
            MultiTenantContextHolder.set(null);
        }

        log.info("found servicename by appName："+appName+"su:"+serviceUnitName+"：");
        if(storageInfo!=null && storageInfo.size()>0){
            storageInfo.forEach(x->{
                log.info(x);
            });
        }

        if (storageInfo == null)
            return null;
        return this.loadBalance.selectService(storageInfo);

    }

    /**
     * 获取应用下所有启用的su信息
     * @return
     */
    @Override
    public List<ServiceUnitInfo> discoverEnableServiceUnitInfo() {
        List<GspMsuRegisterInfo> list = new ArrayList<>();
        try{

            //msu的注册默认注册到主库
            MultiTenantContextInfo contextInfo = new MultiTenantContextInfo();
            contextInfo.setMasterDb(true);
            MultiTenantContextHolder.set(contextInfo);
            list = this.storage.getEnabledServiceUnitInfo();

        }finally {
            MultiTenantContextHolder.set(null);
        }

        var suList = new ArrayList<ServiceUnitInfo>();
        list.forEach(x -> {
            if (suList.stream().noneMatch(su -> su.getName().equals(x.getServiceUnitName()))) {
                ServiceUnitInfo info = new ServiceUnitInfo();
                info.setName(x.getServiceUnitName());
                info.setServiceUnitDes(x.getServiceUnitDes());
                suList.add(info);
            }
        });

        return suList;
    }
}
